package com.luo.gmall.pms.service.impl;

import com.alibaba.csp.sentinel.util.StringUtil;
import com.alibaba.nacos.client.naming.utils.CollectionUtils;
import com.alibaba.nacos.client.utils.StringUtils;
import com.luo.gmall.pms.entity.*;
import com.luo.gmall.pms.api.SmsSaleFeign;
import com.luo.gmall.pms.mapper.SkuMapper;
import com.luo.gmall.pms.mapper.SpuDescMapper;
import com.luo.gmall.pms.service.*;
import com.luo.gmall.pms.vo.SkuVo;
import com.luo.gmall.pms.vo.SpuAttrValueVo;
import com.luo.gmall.pms.vo.SpuVo;
import com.luo.gmall.sms.vo.SmsSaleVo;
import io.seata.spring.annotation.GlobalTransactional;
import lombok.extern.slf4j.Slf4j;
import org.springframework.amqp.rabbit.core.RabbitTemplate;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.util.Date;
import java.util.List;
import java.util.stream.Collectors;

import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.luo.gmall.common.bean.PageResultVo;
import com.luo.gmall.common.bean.PageParamVo;

import com.luo.gmall.pms.mapper.SpuMapper;
import org.springframework.transaction.annotation.Transactional;


@Service("spuService")
@Slf4j
public class SpuServiceImpl extends ServiceImpl<SpuMapper, SpuEntity> implements SpuService {

    @Autowired
    private SpuAttrValueService spuAttrValueService;

    @Autowired
    private SpuDescService spuDescService;

    @Autowired
    private SpuDescMapper spuDescMapper;

    @Autowired
    private SkuMapper skuMapper;

    @Autowired
    private SkuImagesService skuImagesService;

    @Autowired
    private SkuAttrValueService skuAttrValueService;

    @Autowired
    private SmsSaleFeign smsSaleFeign;

    @Autowired
    private RabbitTemplate rabbitTemplate;



    @Override
    public PageResultVo queryPage(PageParamVo paramVo) {
        IPage<SpuEntity> page = this.page(
                paramVo.getPage(),
                new QueryWrapper<SpuEntity>()
        );

        return new PageResultVo(page);
    }

    @Override
    public PageResultVo querySpuByPageAndCategoryId(Long categoryId, PageParamVo paramVo) {
        QueryWrapper<SpuEntity> queryWrapper = new QueryWrapper<>();
        if (categoryId != 0) {
            queryWrapper.eq("category_id", categoryId);
        }
        if (StringUtil.isNotBlank(paramVo.getKey())) {
            queryWrapper.and(q -> q.eq("id", paramVo.getKey()).or().like("name", paramVo.getKey()));
        }
        IPage<SpuEntity> page = this.page(paramVo.getPage(), queryWrapper);
        return new PageResultVo(page);
    }


    /**
     * 发送消息消息的方法
     */
    private void sendMessage(Long id, String type) {
        try {
            rabbitTemplate.convertAndSend("PMS_SPU_EXCHANGE", "item." + type, id);
        } catch (Exception e) {
            log.error("{}商品消息发送异常，商品id：{}", type, id, e);
        }
    }

    @Override
    @GlobalTransactional
    public void bigSave(SpuVo spuVo) {
        // 1.添加spu相关数据
        // 获取添加数据后的spu_id
        Long spuId = saveSpu(spuVo);

//        FileInputStream fileInputStream = new FileInputStream(new File("xxx"));

        // 1.2添加spu_desc数据
        spuDescService.saveSpuDesc(spuVo, spuId);
//        this.saveSpuDesc(spuVo,spuId);

        // 1.3添加spu_attr_value数据
        saveBaseAttr(spuVo, spuId);

        // 2. 保存sku相关信息
        saveSku(spuVo, spuId);

//        int i = 1 / 0;
        // 消费者发送已添加商品信息的id
        sendMessage(spuVo.getId(), "insert");


    }


    /**
     * 保存营销相关的数据
     */
    @Override
    @Transactional(rollbackFor = Exception.class)
    public void saveSku(SpuVo spuVo, Long spuId) {
        List<SkuVo> skuVos = spuVo.getSkus();
        // 判断是否为空
        if (CollectionUtils.isEmpty(skuVos)) {
            return;
        }

        for (SkuVo skuVo : skuVos) {
            // 2.1. 保存sku基本信息
            SkuEntity skuEntity = new SkuEntity();
            BeanUtils.copyProperties(skuVo, skuEntity);
            skuEntity.setSpuId(spuId);
            skuEntity.setBrandId(spuVo.getBrandId());
            skuEntity.setCategoryId(spuVo.getCategoryId());

            List<String> images = skuVo.getImages();
            if (!CollectionUtils.isEmpty(images)) {
                // 有默认图片就用默认图片，否则就用图片集合的第一张图片
                skuEntity.setDefaultImage(skuEntity.getDefaultImage() == null ? images.get(0) : skuEntity.getDefaultImage());
            }
            skuMapper.insert(skuEntity);
            // 返回skuId
            Long skuId = skuEntity.getId();
            // 2.2. 保存sku图片信息
            if (!CollectionUtils.isEmpty(images)) {
                List<SkuImagesEntity> skuImagesEntities = images.stream().map(image -> {
                    SkuImagesEntity skuImagesEntity = new SkuImagesEntity();
                    skuImagesEntity.setSkuId(skuId);
                    skuImagesEntity.setUrl(image);
                    // 判断当前图片是否为默认图片（是否为第一张图片）
                    skuImagesEntity.setDefaultStatus(skuImagesEntity.getUrl().equals(images.get(0)) ? 1 : 0);
                    return skuImagesEntity;
                }).collect(Collectors.toList());
                skuImagesService.saveBatch(skuImagesEntities);
            }
            // 2.3. 保存sku的规格参数（销售属性）
            List<SkuAttrValueEntity> saleAttrs = skuVo.getSaleAttrs();
            if (!CollectionUtils.isEmpty(saleAttrs)) {
                List<SkuAttrValueEntity> skuAttrValueEntities = saleAttrs.stream().map(saleAttr -> {
                    // 设置skuId值
                    saleAttr.setSkuId(skuId);
                    return saleAttr;
                }).collect(Collectors.toList());
                skuAttrValueService.saveBatch(skuAttrValueEntities);
            }

            // 3. 保存营销相关信息，需要远程调用gmall-sms
            SmsSaleVo smsSaleVo = new SmsSaleVo();
            BeanUtils.copyProperties(skuVo, smsSaleVo);
            smsSaleVo.setSkuId(skuId);
            smsSaleFeign.saveSmsSaleVo(smsSaleVo);

            // 3.1. 积分优惠

            // 3.2. 满减优惠

            // 3.3. 数量折扣
        }
    }


    /**
     * 保存基础属性
     */
    @Override
    @Transactional(rollbackFor = Exception.class)
    public void saveBaseAttr(SpuVo spuVo, Long spuId) {
        List<SpuAttrValueVo> attrValueVos = spuVo.getBaseAttrs();
        // 判断是否为空
        if (!CollectionUtils.isEmpty(attrValueVos)) {
            // 将SpuAttrValueVo集合转换成SpuAttrValue集合
            List<SpuAttrValueEntity> spuAttrValueEntities = attrValueVos.stream().map(spuAttrValueVo -> {
                spuAttrValueVo.setSpuId(spuId);
                return spuAttrValueVo;
            }).collect(Collectors.toList());
            //添加多条数据
            spuAttrValueService.saveBatch(spuAttrValueEntities);
        }
    }

    /**
     * 保存spu描述的数据
     */
    @Override
    @Transactional(rollbackFor = Exception.class)
    public void saveSpuDesc(SpuVo spuVo, Long spuId) {
        List<String> spuImages = spuVo.getSpuImages();
        // 判断是否为空
        if (!CollectionUtils.isEmpty(spuImages)) {
            SpuDescEntity spuDescEntity = new SpuDescEntity();
            spuDescEntity.setSpuId(spuId);
            spuDescEntity.setDecript(StringUtils.join(spuImages, ";"));
            spuDescMapper.insert(spuDescEntity);
        }
    }

    /**
     * 保存spu相关的数据
     */
    @Override
    @Transactional(rollbackFor = Exception.class)
    public Long saveSpu(SpuVo spuVo) {
        // 1.1添加spu数据
        // 设置添加时间和修改时间
        spuVo.setCreateTime(new Date());
        spuVo.setUpdateTime(spuVo.getCreateTime());
        this.save(spuVo);
        return spuVo.getId();
    }


}